<?php

namespace app\api\service;

use app\api\model\AdminModel;
use app\api\model\CategoryModel;
use app\api\model\CompanyModel;
use app\api\model\ProductChannelModel;
use app\api\model\ProductModel;
use think\Db;
use think\Exception;
use think\Request;
use think\Validate;

class ProductService extends Api
{
    protected static $instance;

    public function __construct(Request $request = null)
    {
        parent::__construct($request);
    }

    public static function getInstance()
    {
        if (is_null(self::$instance))
        {
            self::$instance = new static();
        }
        return self::$instance;
    }

    /**
     * 获取产品基础配置信息
     */
    public function getProductBase($params, $data = [])
    {
        $Validate = new Validate([
            'identi' => 'require'
        ], [
            'identi' => '缺少产品标识'
        ]);
        if (!$Validate->check($params))
        {
            $this->error($Validate->getError());
        }

        $proCode = self::getProductNum();

        $proInfo = [];
        if (!empty($params['id']))
        {
            $pInfo = ProductModel::getInstance()->find($params['id']);
            $proCode = $pInfo['product_code'];
            $proInfo = self::getProductInfo($params['id']);
        }

        $config = self::getProductConfig($params['identi'], $proInfo);
        if (!$config)
        {
            $this->error('当前险种类别未开放，无可用配置，请联系系统管理员后操作');
        }
        array_unshift($config[1], [
            'title' => '产品代码',
            'name' => 'product_code',
            'cate' => 'input',
            'value' => '',
            'select' => $proCode
        ]);
        return [
            'proCode' => $proCode,
            'proInfo' => $config,
        ];
    }

    /**
     * 变更产品信息
     */
    public function changeProduct($params)
    {
        self::checkProduct($params);//校验产品信息

        Db::startTrans();
        try{
            //组装产品数据
            $saveData = self::assembleProduct($params);
            $saveData['baseData']['identi'] = $params['identi'];
            if (!empty($params['id']))
            {
                $proId = $params['id'];
                $saveData['baseData']['u_time'] = datetime(time(), 'Y-m-d H:i:s');
                $res = ProductModel::getInstance()->updateBase($proId, $saveData['baseData']);
            }else{
                $saveData['baseData']['c_id'] = $this->uid;
                $saveData['baseData']['c_time'] = datetime(time(), 'Y-m-d H:i:s');
                $res = $proId = ProductModel::getInstance()->insertBase($saveData['baseData']);
            }

            if ($res)
            {
                foreach ($saveData['extendData'] as $k => $v)
                {
                    $sData = [
                        'pro_id' => $proId,
                        'field' => $k,
                        'content' => $v,
                    ];
                    if (!empty($params['id']))
                    {
                        $sData['u_time'] = datetime(time(), 'Y-m-d H:i:s');
                    }else{
                        $sData['c_time'] = datetime(time(), 'Y-m-d H:i:s');
                    }
                    $configData[] = $sData;
                }
                ProductModel::getInstance()->deleteAll($params['id']);
                ProductModel::getInstance()->insertAll($configData);
                LogService::getInstance()->writeSysLog([
                    'operation' => '/api/product/changeProduct',
                    'title' => !empty($params['id']) ? '编辑' : '添加',
                    'content' => $params,
                ]);
                Db::commit();
                return $res;
            }else{
                Db::rollback();
                $this->error('编辑产品信息失败');
            }
        }catch (Exception $e)
        {
            Db::rollback();
            $this->error($e->getMessage());
        }
    }

    /**
     * 组装产品数据
     */
    public function assembleProduct($params)
    {
        $ValidateArr = ProductModel::getInstance()->getProductConfig();
        foreach ($params as $k => $v)
        {
            if (in_array($k, ['product_name','product_code','product_status','product_cate','company','product_num','sort','payment_method','is_insure_file','product_class']))
            {
                $baseData[$k] = is_array($v) ? json_encode($v) : $v;
            }else{
                foreach ($ValidateArr as $kk => $vv)
                {
                    if ($params['identi'] == $vv['identi'] && $k == $vv['name'])
                    {
                        $extendData[$k] = is_array($v) ? json_encode($v) : $v;
                    }
                }
            }
        }
        return [
            'baseData' => $baseData,
            'extendData' => $extendData,
        ];
    }

    /**
     * 产品规则验证
     */
    public function checkProduct($params)
    {
        $ValidateArr = ProductModel::getInstance()->getProductConfig();
        $Validate = new Validate([
            'identi' => 'require',
            'product_code' => 'require',
        ], [
            'identi' => '缺少产品标识',
            'product_code' => '缺少产品代码',
        ]);
        if (!$Validate->check($params))
        {
            $this->error($Validate->getError());
        }
        $validateCheck = $validateMsg = [];
        foreach ($ValidateArr as $k => $v)
        {
            if ($v['is_must'])
            {
                switch ($v['name'])
                {
                    case 'sort':
                        $validateCheck[$v['name']] = 'require';
                        $validateMsg[$v['name']] = '缺少'.$v['title'];
                        break;
                    default:
                        $validateCheck[$v['name']] = 'require';
                        $validateMsg[$v['name']] = '缺少'.$v['title'];
                        break;
                }
            }
        }
        $validate = new Validate($validateCheck, $validateMsg);
        if (!$validate->check($params))
        {
            $this->error($validate->getError());
        }
        return true;
    }

    /**
     * 获取指定产品信息
     */
    public function getProductInfo($id)
    {
        $baseInfo = ProductModel::getInstance()->find(intval($id), 'product_name,product_code,product_status,product_cate,company,product_num,sort,payment_method,is_insure_file,product_class');
        $extendInfo = ProductModel::getInstance()->columnInfo($id, 'content');
        return array_merge($baseInfo, $extendInfo);
    }

    /**
     * 获取产品分类
     */
    public function getProductCate($params)
    {
        $Validate = new Validate([
            'identi' => 'require'
        ], [
            'identi' => '缺少产品标识'
        ]);
        if (!$Validate->check($params))
        {
            $this->error($Validate->getError());
        }
        $cate = CategoryModel::getInstance()->select([
            'identi' => ['eq', $params['identi']]
        ], 'id,title');
        return $cate;
    }

    /**
     * 获取指定类别基础信息字段
     */
    public function getProductConfig($identi, $proInfo = [])
    {
        $list = ProductModel::getInstance()->select([
            'identi' => ['eq', $identi],
            'status' => ['eq', 1]
        ]);

        $result = [];
        foreach ($list as $k => $v)
        {
            $value = '';
            $select = isset($proInfo[$v['name']]) ? (strpos($proInfo[$v['name']], '{') !== false ? json_decode($proInfo[$v['name']], true) : $proInfo[$v['name']]) : '';
            switch ($v['name'])
            {
                case 'product_cate':
                    $value = CategoryModel::getInstance()->column([
                        'identi' => ['eq', $identi]
                    ], 'title');
                    break;
                case 'company':
                    $value = CompanyModel::getInstance()->column([], 'name');
                    break;
                case 'product_class':
                    $value = json_decode($v['value'], true);
                    break;
                case 'product_status':
                    $value = json_decode($v['value'],true);
                    break;
                case 'product_label':
                    $value = json_decode($v['value'], true);
                    if (isset($proInfo[$v['name']]))
                    {
                        $select = json_decode($proInfo[$v['name']], true);
                    }
                    break;
                case 'insure_type':
                    $value = json_decode($v['value'], true);
                    if (isset($proInfo[$v['name']]))
                    {
                        $select = json_decode($proInfo[$v['name']], true);
                    }
                    break;
                case 'is_insure_file':
                    $value = [
                        0 => '否',
                        1 => '是'
                    ];
                    break;
                case 'is_amends_insure_file':
                    $value = [
                        0 => '否',
                        1 => '是'
                    ];
                    $select = intval($select);
                    break;
                case 'payment_method':
                    $value = json_decode($v['value'], true);/*[
                        1 => '线上支付',
                        2 => '线下支付',
                    ];*/
                    break;
            }
            $result[$v['tab']][] = [
                'title' => $v['title'],
                'name' => $v['name'],
                'cate' => $v['cate'],
                'value' => $value,
                'is_must' => $v['is_must'],
                'select' => $select//$v['name'] == 'is_insure_file' ? intval($select) : ($v['name'] == 'payment_method' ? $select.'' : $select)
            ];
        }
        return $result;
    }

    /**
     * 获取产品列表
     */
    public function getProductList($params)
    {
        $Validate = new Validate([
            'identi' => 'require'
        ], [
            'identi' => '缺少产品标识'
        ]);
        if (!$Validate->check($params))
        {
            $this->error($Validate->getError());
        }

        $page = $this->request->param('page', 1);
        $limit = $this->request->param('limit', 15);
        $start = ($page - 1) * $limit;

        $where = [
            'identi' => ['eq', $params['identi']]
        ];

        if ($this->uid > 1)
        {
            $adminIds = AdminModel::getInstance()->select([], 'id,username,nickname,pid', 0, 1000000);
            $adminIds = MenuService::getInstance()->getChildIds($adminIds, [$this->uid]);
            $teamId = AdminModel::getInstance()->value([
                'id' => ['eq', $this->uid]
            ], 'team');
            $groupAdminIds = AdminModel::getInstance()->column([
                'team' => ['eq', $teamId],
            ], 'id');
            $adminIds = array_merge($adminIds, $groupAdminIds);
            //查询当前登录账号可见产品
            $adminProIds = ProductModel::getInstance()->selectProduct([
                'c_id' => ['in', $adminIds]
            ], 'id');

            $channelProIds = [];/*ProductChannelModel::getInstance()->select([
                'admin_id' => ['eq', $this->uid],
                'status' => ['eq', 1]
            ], 'product_id,commission_type,promotion_commission,step_commission,status');*/
            $proIds = array_merge(array_column($adminProIds, 'id'), array_column($channelProIds, 'product_id'));
            $where['id'] = ['in', $proIds];
        }

        if (!empty($params['product_name']))
        {
            $where['product_name'] = ['like', '%'.$params['product_name'].'%'];
        }
        if (!empty($params['product_code']))
        {
            $where['product_code'] = ['like', '%'.$params['product_code'].'%'];
        }
        if (!empty($params['product_num']))
        {
            $where['product_num'] = ['like', '%'.$params['product_num'].'%'];
        }
        if (!empty($params['product_status']))
        {
            $where['product_status'] = ['eq', $params['product_status']];
        }
        if (!empty($params['product_cate']))
        {
            $where['product_cate'] = ['eq', $params['product_cate']];
        }
        if (!empty($params['company']))
        {
            $where['company'] = ['eq', $params['company']];
        }

        $total = ProductModel::getInstance()->countProduct($where);
        $list = ProductModel::getInstance()->selectProduct($where, '*', $start, $limit);

        foreach ($list as $k => $v)
        {
            $list[$k]['company'] = CompanyModel::getInstance()->value([
                'id' => ['eq', $v['company']]
            ]);
            $list[$k]['product_status'] = json_decode(ProductModel::getInstance()->value([
                'name' => ['eq', 'product_status']
            ]), true)[$v['product_status']];
            $list[$k]['product_cate'] = CategoryModel::getInstance()->value([
                'id' => ['eq', $v['product_cate']]
            ], 'title');
            $list[$k]['payment_method'] = json_decode(ProductModel::getInstance()->value([
                'name' => ['eq', 'payment_method']
            ]), true)[$v['payment_method']];
        }
        return [
            'total' => $total,
            'list' => $list
        ];
    }
}